package com.sd.repay.transfer.bank;

import com.alibaba.fastjson.JSONObject;
import com.sd.repay.common.CommonResult;
import com.sd.repay.pojo.TransferChannelInfo;
import com.sd.repay.pojo.TransferOrder;
import com.sd.repay.transfer.TransferChannelCache;
import com.sd.repay.utils.*;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.util.HashMap;
import java.util.Map;

/**
 * 洋仆淘-代付
 *
 * @author
 */
@Service
public class YPTPayService extends BaseRepayService {

    private Logger log = LoggerFactory.getLogger(YPTPayService.class);

    private String channelName = "洋仆淘";

    private final String channelNo = "S99HHZTP";


    @Override
    public CommonResult channelCheck(TransferOrder order) {
        CommonResult result = new CommonResult();

        String bankName = order.getInBankName();
        if (StringUtil.isBlank(bankName)) {
            result.setStatus(2);
            result.setMsg("缺少银行名称");
            return result;
        }
        result.setStatus(1);
        return result;
    }

    @Override
    public void transferOrder(TransferOrder order) {
        log.info(channelName.concat("代付[{}]执行开始"), order.toJsonString());
        String status = "";
        String resultCode = "";
        String resultMsg = "";
        String orderNo = "";
        String acqOrderNo = "";
        try {
            orderNo = getOrderNo(order);
            TransferChannelInfo channelInfo = (TransferChannelInfo) TransferChannelCache.getChannel(order.getOutPayBank() + order.getOutAccNo());

            BigDecimal amount = order.getAmount();
            String userNo = order.getAcqMerNo();
            String key = channelInfo.getEncryptionKey();
            String url = channelInfo.getPayUrl();
            String merNo = channelInfo.getBankMerchantNo();
            String busiCode = channelInfo.getPayBusinessType();

            CommonResult result = entryCardConfirm(orderNo, userNo, busiCode, userNo, key);
            if (result.getStatus() == 1) {
                String token = result.getMsg();
                Map<String, String> sendMap = new HashMap<>();
                sendMap.put("merchant_no", merNo);                        //渠道商商户号YPT分配的渠道商户号
                sendMap.put("channel_no", channelNo);                    //固定值 ‘S99HHZTP
                sendMap.put("business_no", busiCode);                    //固定值 ‘agency_pay_channel
                sendMap.put("user_no", userNo);                            //商户入网返回的 user_no
                sendMap.put("config_no", token);                    //渠道激活的配置号
                sendMap.put("order_no", orderNo);                        //订单号商户自定义不重复订单号长度不小于16位
                sendMap.put("notifyUrl", "notifyUrl");                    //渠道商接受回调路由,用于异步接受通知
                sendMap.put("price", amount.toPlainString());            //订单金额 单位元(1 = 人民币 1元)

                String signStr = ParamUtil.getOrderedParas(sendMap);
                signStr = signStr.concat("&key=").concat(key);
                String sign = Md5Util.MD5Encode(signStr, enCode, true);
                sendMap.put("sign", sign);                                //签名

                String resultStr = HttpClientUtil.doPost(url, sendMap, enCode);
                log.info(channelName.concat("代付[{}], 渠道响应[{}]"), sendMap.toString(), resultStr);
                order.setBak1(token);
                if (StringUtils.isBlank(resultStr)) {
                    status = "2";
                    resultCode = "response is null";
                    resultMsg = "*代付渠道未响应";
                } else {

                    JSONObject resultJson = null;
                    try {
                        resultJson = JSONObject.parseObject(resultStr);
                    } catch (Exception e) {
                        log.error(channelName.concat("代付[{}]渠道响应错误的JSON报文格式[{}]"), order.toJsonString(), resultStr);
                        status = "2";
                        resultCode = "real error";
                        resultMsg = "*代付出现错误,渠道响应报文格式异常";
                    }

                    if (resultJson != null) {
                        String code = StringUtils.defaultString(resultJson.getString("Code"));
                        String msg = StringUtils.defaultString(resultJson.getString("Msg"));
                        String resp_code = StringUtils.defaultString(resultJson.getString("Resp_code"));
                        String resp_msg = StringUtils.defaultString(resultJson.getString("Resp_msg"));
                        String authent_no = StringUtils.defaultString(resultJson.getString("ypt_order_no"));

                        if ("10000".equals(code)) {

                            if ("40000".equals(resp_code)) {
                                status = "1";
                            } else {
                                status = "2";
                            }

                            acqOrderNo = authent_no;
                            resultCode = resp_code;
                            resultMsg = resp_msg;

                        } else {
                            status = "2";
                            resultCode = code;
                            resultMsg = msg;
                        }
                    }
                }
            } else {
                status = "2";
                resultCode = result.getStatus() + "";
                resultMsg = result.getMsg();
            }


        } catch (Exception e) {
            log.error(channelName.concat("代付[{}]执行出现异常:{}"), order.toJsonString(), e.getMessage());
            status = "1";
            resultCode = "submit transfer error";
            resultMsg = "*提交代付出现错误";
        }

        order.setStatus(status);
        order.setSubResultCode(resultCode);
        order.setSubResultMsg(resultMsg);
        order.setSubOrderNo(orderNo);
        order.setAcqOrderNo(acqOrderNo);
        log.info(channelName.concat("代付[{}]执行结束"), order.toJsonString());
    }

    @Override
    public void queryTransferStatus(TransferOrder order) {
        log.info(channelName.concat("同步代付状态[{}]执行开始"), order.toJsonString());
        String status = "";
        String resultCode = "";
        String resultMsg = "";
        String acqOrderNo = "";
        try {
            acqOrderNo = order.getAcqOrderNo();
            TransferChannelInfo channelInfo = (TransferChannelInfo) TransferChannelCache.getChannel(order.getOutPayBank() + order.getOutAccNo());
            String key = channelInfo.getEncryptionKey();
            String url = channelInfo.getQueryUrl();
            String merNo = channelInfo.getBankMerchantNo();
            String busiCode = channelInfo.getPayBusinessType();

            Map<String, String> sendMap = new HashMap<>();
            sendMap.put("merchant_no", merNo);                        //渠道商商户号YPT分配的渠道商户号
            sendMap.put("channel_no", channelNo);                    //固定值 ‘S99HHZTP
            sendMap.put("business_no", busiCode);                    //固定值 ‘agency_pay_channel
            sendMap.put("ypt_order_no", acqOrderNo);                //YPT 订单号

            String signStr = ParamUtil.getOrderedParas(sendMap);
            signStr = signStr.concat("&key=").concat(key);
            String sign = Md5Util.MD5Encode(signStr, enCode, true);
            sendMap.put("sign", sign);                                //签名

            String resultStr = HttpClientUtil.doPost(url, sendMap, enCode);
            log.info(channelName.concat("代付[{}], 渠道响应[{}]"), sendMap.toString(), resultStr);

            if (StringUtils.isBlank(resultStr)) {
                status = "2";
                resultCode = "response is null";
                resultMsg = "*代付渠道未响应";
            } else {

                JSONObject resultJson = null;
                try {
                    resultJson = JSONObject.parseObject(resultStr);
                } catch (Exception e) {
                    log.error(channelName.concat("代付[{}]渠道响应错误的JSON报文格式[{}]"), order.toJsonString(), resultStr);
                    status = "2";
                    resultCode = "real error";
                    resultMsg = "*代付出现错误,渠道响应报文格式异常";
                }

                if (resultJson != null) {
                    String code = StringUtils.defaultString(resultJson.getString("Code"));
                    String msg = StringUtils.defaultString(resultJson.getString("Msg"));
                    String resp_code = StringUtils.defaultString(resultJson.getString("Resp_code"));
                    String resp_msg = StringUtils.defaultString(resultJson.getString("Resp_msg"));
                    String authent_no = StringUtils.defaultString(resultJson.getString("ypt_order_no"));

                    if ("10000".equals(code)) {

                        if ("40000".equals(resp_code)) {
                            status = "1";
                        } else {
                            status = "2";
                        }

                        acqOrderNo = authent_no;
                        resultCode = resp_code;
                        resultMsg = resp_msg;

                    } else {
                        status = "2";
                        resultCode = code;
                        resultMsg = msg;
                    }
                }
            }
        } catch (Exception e) {
            log.error(channelName.concat("代付[{}]执行出现异常:{}"), order.toJsonString(), e.getMessage());
            status = "1";
            resultCode = "submit transfer error";
            resultMsg = "提交代付出现错误";
        }

        order.setStatus(status);
        order.setSubResultCode(resultCode);
        order.setSubResultMsg(resultMsg);
        log.info(channelName.concat("同步代付状态[{}]执行开始"), order.toJsonString());
        int count = transferService.modifySysStaTransfer(order);
        log.info(channelName.concat("出款订单号[{}] 同步结果[{}], 渠道响应[{}：{}], [{}]条记录受到影响"), new Object[]{order.getSubOrderNo(), order.getStatus(), order.getResultCode(), order.getResultMsg(), order.getId(), count});
    }


    /**
     * 激活
     *
     * @param orderNo    订单编号
     * @param acqMerNo   出款账户
     * @param businessNo 业务编号
     * @param userNo     渠道子商户编号
     * @param key        签名密钥
     * @return
     */
    private CommonResult entryCardConfirm(String orderNo, String acqMerNo, String businessNo, String userNo, String key) {
        log.info(channelName.concat("订单号[{}] 激活开始执行"), orderNo);
        CommonResult result = new CommonResult();
        Map<String, String> sendMap = new HashMap<>();
        sendMap.put("merchant_no", acqMerNo);                    //渠道商商户号YPT分配的渠道商户号
        sendMap.put("channel_no", channelNo);                    //固定值 ‘S99HHZTP
        sendMap.put("business_no", businessNo);                    //固定值 ‘agency_pay_channel
        sendMap.put("user_no", userNo);                            //YPT 订单号

        String signStr = ParamUtil.getOrderedParas(sendMap);
        signStr = signStr.concat("&key=").concat(key);
        String sign = Md5Util.MD5Encode(signStr, enCode, true);
        sendMap.put("sign", sign);                                //签名
        try {
            String resultStr = HttpClientUtil.doPost(WebUtil.getSysValue(""), sendMap, enCode);
            log.info(channelName.concat("订单号[{}] 激活请求原文[{}], 渠道响应[{}]"), orderNo, sendMap.toString(), resultStr);
            if (StringUtils.isBlank(resultStr)) {
                result.setStatus(2);
                result.setMsg("*代付激活渠道响应未响应");
                return result;
            } else {

                JSONObject resultJson = null;
                try {
                    resultJson = JSONObject.parseObject(resultStr);
                } catch (Exception e) {
                    log.error(channelName.concat("订单号[{}] [激活] 渠道响应错误的JSON报文格式[{}]"), orderNo, resultStr);
                    result.setStatus(2);
                    result.setMsg("*代付激活渠道响应报文格式错误");
                    return result;
                }

                String code = StringUtils.defaultString(resultJson.getString("Code"));
                String msg = StringUtils.defaultString(resultJson.getString("Msg"));
                String resp_code = StringUtils.defaultString(resultJson.getString("Resp_code"));
                String resp_msg = StringUtils.defaultString(resultJson.getString("Resp_msg"));
                String config_no = StringUtils.defaultString(resultJson.getString("config_no"));

                if ("10000".equals(code)) {
                    if ("40000".equals(resp_code)) {
                        result.setStatus(1);
                        result.setMsg(config_no);
                        return result;
                    } else {
                        result.setStatus(2);
                        result.setMsg(resp_msg);
                        return result;
                    }
                } else {
                    result.setStatus(2);
                    result.setMsg(msg);
                    return result;
                }
            }
        } catch (Exception e) {
            log.error(channelName.concat("订单号[{}]激活出现异常:{}"), e.getMessage());
            result.setStatus(2);
            result.setMsg("*激活出现错误");
            return result;
        }
    }

}
